package zb.WX.util;

import com.google.gson.Gson;
import zb.WX.bean.accessToken.AccessToken;

import javax.net.ssl.HttpsURLConnection;
import java.io.*;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Date;

/*
 * 该方法实现获取Access_token、保存并且只保存2小时Access_token。如果超过两个小时重新获取；如果没有超过两个小时，直接获取，一天最多获取13次。
 *
 */
public class AccessTokenSaveUtil {
    /*
     * 将获取到的access_token保存到本地。按上面的规则获取
     * 此方法依赖于refershAccesstoken()方法
     * 思路:
     * 将获取到的Access_token和当前时间存储到file里，express_in为当时获取的系统时间，
     * 取出时判断当前时间和存储里面的记录的时间的时间差，如果大于MAX_TIME,重新获取，并且将获取到的存储到file替换原来的内容
     * 如果小于MAX_TIME，直接从文件中获取。
     */
    public static String getLocationAccesstonken() {
        FileInputStream fis = null;
        FileOutputStream fos = null;
        String result = null;
        Gson gson = new Gson();
        File file = new File(PropertiesUtil.getPropValue("accessTokenFile"));
        if (!file.exists()) {
            try {
                file.createNewFile();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }

        if (file.length() == 0) {//如果文件中没有内容则发送get请求获取accesstoken并将其存入文件
            result = AccessTokenSaveUtil.refershAccesstoken();
            try {
                fos = new FileOutputStream(file, false);//不追加内容，直接覆盖
                AccessToken at = new AccessToken();
                at.setAccess_token(result);
                at.setExpires_in(new Date().getTime());
                String accessTokenJson = gson.toJson(at);
                fos.write(accessTokenJson.getBytes());//将获取到的accesstoken存储到文件
                fos.close();
            } catch (FileNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            System.out.println("第一次获取创建文，并获取到了access_token");
            return result;
        } else {//获取文件中的access_token
            byte[] b = new byte[1024];
            try {
                fis = new FileInputStream(file);
                int len = 0;
                result = "";
                while ((len = fis.read(b)) != -1) {
                    result += new String(b, 0, len);
                }
                AccessToken accessToken = gson.fromJson(result, new AccessToken().getClass());
                if (accessToken.getExpires_in() != null) {
                    long overtime = System.currentTimeMillis() - accessToken.getExpires_in();
                    if (GlobalVar.EXPIRES_IN * 1000 < overtime) {//如果超过2小时，发送请求获取access_token
                        result = AccessTokenSaveUtil.refershAccesstoken();
                        fos = new FileOutputStream(file, false);//不追加内容，直接覆盖
                        AccessToken at = new AccessToken();
                        at.setAccess_token(result);//重新获取access_token
                        at.setExpires_in(new Date().getTime());
                        String accessTokenJson = gson.toJson(at);
                        fos.write(accessTokenJson.getBytes());//将获取到的accesstoken存储到文件
                        fos.close();
                        System.out.println("超时获取到了access_token");
                    } else {//没有超过两个小时直接文件中获取accesstoken
                        System.out.println("从文件中获取到了access_token");
                        return accessToken.getAccess_token();
                    }
                } else {
                    return null;
                }
            } catch (FileNotFoundException e) {
                e.printStackTrace();
            } catch (IOException e) {
                e.printStackTrace();
            }
            return result;
        }
    }

    /**
     * 请求微信服务端获取到的accesstoken格式如下:
     * {"access_token":"ACCESS_TOKEN","expires_in":7200}
     * 是一个json类型的字符串，我们用Gson（第三方jar包）将其转化为AccessToken实体对象，然后获取access_token
     *
     * @return
     */

    public static String refershAccesstoken() {
        String accessTokenUrl = GlobalVar.ACCESS_TOKEN_URL.replace("APPID", GlobalVar.APPID).replace("APPSECRET", GlobalVar.APPSECRET);
        String result = null;
        InputStreamReader isr = null;
        try {
            URL url = new URL(accessTokenUrl);//将获取accss_token的地址当成参数传递进去
            HttpsURLConnection httpsConn = (HttpsURLConnection) url.openConnection();//建立一个url链接
            isr = new InputStreamReader(httpsConn.getInputStream());//获取请求之后获取到的流
            //将流转化为字符串
            char[] c = new char[1024];
            int len;
            result = "";
            while ((len = isr.read(c)) != -1) {
                result += new String(c, 0, len);
            }
        } catch (MalformedURLException e) {
            e.printStackTrace();
        } catch (IOException e) {
            e.printStackTrace();
        } finally {
            try {
                isr.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        //将得到的字符串转化为java实体类对象
        Gson gson = new Gson();
        AccessToken accessToken = gson.fromJson(result, new AccessToken().getClass());//将获取到的
        if (accessToken != null) {
            return accessToken.getAccess_token();
        } else {
            System.out.println("刷新access_token失败");
            return null;
        }
    }

}
